﻿//////////////////////////////////////////////////////////////////////////////
//
//  Copyright © 1998-2024 Glodon Company Limited.  All rights reserved.
//
//  Use of this software is subject to the terms of the Glodon license
//  agreement provided at the time of installation or download, or which
//  otherwise accompanies this software in either electronic or hard copy form.  
//
//////////////////////////////////////////////////////////////////////////////


#pragma once
#include "GcmpDatabase.h"
#include "GbmpTypeDefs.h"
#include "ClassId.h"
#include "NdbClassSchemaLibrary.h"
#include <unordered_set>
#include <unordered_map>

namespace gcmp
{
    class NdbClassSchema;
    class NdbClassSchemaLibraryOfCode;

    class NdbClassSchemaLibraryOfFile : public NdbClassSchemaLibrary
    {
        DEFINE_CAST_DERIVED(gcmp::NdbClassSchemaLibraryOfFile, gcmp::NdbClassSchemaLibrary)
    public:
        friend NdbClassSchema;

        NdbClassSchemaLibraryOfFile(UInt32 fileMajorVersion);

        virtual UInt32 GetClassSchemaCount() const override;

        virtual UInt32 GetMajorVersion() const override { return m_fileMajorVersion; }

        virtual NdbClassSchema * AddClassSchema(gcmp::OwnerPtr<NdbClassSchema> opClassSchema) override;

        virtual bool GetClassIdByIndex(UInt32 index, ClassId & classId) const override;

        virtual const NdbClassSchema* GetSchemaByClassId(const ClassId & classId) const override;

        virtual bool BuildClassHierarchy() override;

        virtual bool IncreaseBuildClassHierarchy(NdbClassSchema * pBuildingClassSchema) override;

        virtual std::wstring GetName() const override { return L"ClassSchemaLibraryOfFile"; }

    public:
        std::pair<bool, std::wstring> Validate(bool & needUpgrade) ;

        std::vector<NdbClassSchema*> GetAllClassSchemasFW();

        void IgnoreClassSchemaOfModules();

        void SetUseClassIdAsSchemaIndice(bool useClassIdAsSchemaIndice) { m_useClassIdAsSchemaIndice = useClassIdAsSchemaIndice; }

        bool GetUseClassIdAsSchemaIndice() const { return m_useClassIdAsSchemaIndice; }

    private:
        friend class NdbClassSchemaLibraryUtils;

        NdbClassSchema* GetSchemaByClassIdFW(const ClassId & classId);

        std::pair<bool, std::wstring> DoClassSchemasExist(bool & needUpgrade);

        //从ClassSchemaLibraryOfCode中去除moduleGuids模块所有类Schema以及所有classIds的类Schema
        void EraseClassSchemas(const std::vector<Guid>& moduleGuids, const std::vector<ClassId>& classIds);

        UInt32 m_fileMajorVersion;

        // Index到ClassId的映射。已知Index时加速查找用
        std::unordered_map<UInt32, ClassId> m_indexToClassIdMap;

        // 以ClassId为索引，存放ClassSchema
        std::unordered_map<ClassId, OwnerPtr<NdbClassSchema>, ClassIdHasher> m_classSchemasOfFileMap;

        bool m_useClassIdAsSchemaIndice;
    };
}
